package com.amanda.reggie.service.impl;

import com.amanda.reggie.common.CustomException;
import com.amanda.reggie.common.R;
import com.amanda.reggie.dto.DishDto;
import com.amanda.reggie.entity.Category;
import com.amanda.reggie.entity.Dish;
import com.amanda.reggie.entity.DishFlavor;
import com.amanda.reggie.entity.SetmealDish;
import com.amanda.reggie.mapper.DishMapper;
import com.amanda.reggie.service.CategoryService;
import com.amanda.reggie.service.DishFlavorService;
import com.amanda.reggie.service.DishService;
import com.amanda.reggie.service.SetmealDishService;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.stream.Collectors;

/**
 * @author amanda
 * @Description 菜品业务实现
 */
@Service
@Slf4j
public class DishServiceImpl extends ServiceImpl<DishMapper, Dish> implements DishService {

    @Autowired
    private DishService dishService;

    @Autowired
    private DishFlavorService dishFlavorService;

    @Autowired
    private CategoryService categoryService;

    @Autowired
    private SetmealDishService setmealDishService;

    /**
     * 新增菜品，保存菜品回味数据
     */
    @Override
    @Transactional
    public void saveWithFlavor(DishDto dishDto) {
        // 1、保存菜品基本信息到dish
        this.save(dishDto);
        // 2、处理dish_id
        Long dishId = dishDto.getId();
        List<DishFlavor> flavors = dishDto.getFlavors();
        flavors = flavors.stream().map((dishFlavor)->{
            dishFlavor.setDishId(dishId);
            return dishFlavor;
        }).collect(Collectors.toList());
        // 2、保存口味数据到dish_flavor
        dishFlavorService.saveBatch(flavors);
    }

    /**
     * 回显菜品数据
     */
    @Override
    public DishDto queryWithFlavorById(Long id) {
        // 1、查询菜品基本信息
        Dish dish = this.getById(id);
        // 2、对象拷贝
        DishDto dishDto = new DishDto();
        BeanUtils.copyProperties(dish, dishDto);
        // 3、对应口味
        LambdaQueryWrapper<DishFlavor> dishFlavorQueryWrapper = new LambdaQueryWrapper<>();
        dishFlavorQueryWrapper.eq(DishFlavor::getDishId, dish.getId());
        List<DishFlavor> flavors = dishFlavorService.list(dishFlavorQueryWrapper);
        dishDto.setFlavors(flavors);
        return dishDto;
    }

    /**
     * 更新菜品
     */
    @Override
    public void updateDish(DishDto dishDto) {
        // 1、清理当前菜品对象口味数据
        LambdaQueryWrapper<DishFlavor> dishFlavorQueryWrapper = new LambdaQueryWrapper<>();
        dishFlavorQueryWrapper.eq(DishFlavor::getDishId, dishDto.getId());
        dishFlavorService.remove(dishFlavorQueryWrapper);
        // 2、添加口味数据
        List<DishFlavor> flavors = dishDto.getFlavors();
        // 3、处理dish_id
        flavors  = flavors.stream().map((dishFlavor) -> {
            dishFlavor.setDishId(dishDto.getId());
            return dishFlavor;
        }).collect(Collectors.toList());
        dishFlavorService.saveBatch(flavors);
        // 4、更新dish表基本信息
        this.updateById(dishDto);
    }

    /**
     * 删除菜品
     */
    @Override
    @Transactional
    public void remove(List<Long> ids) {

        // 1、先查询菜品状态，能否删除
        LambdaQueryWrapper<Dish> dishQueryWrapper = new LambdaQueryWrapper<>();
        dishQueryWrapper.in(Dish::getId, ids);
        dishQueryWrapper.eq(Dish::getStatus, 1);
        int count = this.count(dishQueryWrapper);
        if (count > 0) {
            throw new CustomException("该菜品正在启售中，不能删除！");
        }
        // 2、查询当前菜品的口味数据
        LambdaQueryWrapper<DishFlavor> dishFlavorQueryWrapper = new LambdaQueryWrapper<>();
        // 2.1 添加查询条件
        dishFlavorQueryWrapper.eq(DishFlavor::getDishId, ids);
        // 2.2 删除口味数据
        dishFlavorService.remove(dishFlavorQueryWrapper);

        // 3、查询当前菜品是否关联了套餐
        LambdaQueryWrapper<SetmealDish> setmealQueryWrapper = new LambdaQueryWrapper<>();
        // 3.1 添加查询条件
        setmealQueryWrapper.eq(SetmealDish::getDishId, ids);
        int setmealCount = setmealDishService.count(setmealQueryWrapper);
        if (setmealCount > 0) {
            // 3.2 如果已经关联则抛出业务异常
            throw new CustomException("该菜品正由套餐售卖，不能删除！");
        }
        // 4、正常删除，构造条件查询器
        LambdaQueryWrapper<Dish> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.in(ids != null, Dish::getId, ids);
        // 4.1 逐个删除
        List<Dish> list = this.list(queryWrapper);
        for (Dish dish : list) {
            this.removeById(dish.getId());
        }

    }

    /**
     * 修改菜品状态
     */
    @Override
    @Transactional
    public void updateDishStatusById(Dish dish) {
        // 1、查询当前菜品是否关联了套餐
        LambdaQueryWrapper<SetmealDish> setmealQueryWrapper = new LambdaQueryWrapper<>();
        // 2.1 添加查询条件
        setmealQueryWrapper.eq(SetmealDish::getDishId, dish.getId());
        int setmealCount = setmealDishService.count(setmealQueryWrapper);
        if (setmealCount > 0) {
            if (dish.getStatus() == 0) {
                // 2.2 如果已经关联，并且是停售菜品，则抛出业务异常
                throw new CustomException("当前菜品有套餐正在供应，还有剩余，不能停售！");
            }else {
                // 2.3 后端mysql调试数据，起售菜品
                dishService.updateById(dish);
            }
        }
        dishService.updateById(dish);
    }

    /**
     * 菜品信息分页
     */
    @Override
    public Page<DishDto> pageQuery(int page, int pageSize, String name) {
        // 这里使用mp无法进行复杂查询（待改进）
        // select dish.id, dish.name, category_id, dish.price, dish.code, dish.description, dish.status, dish.sort, dish.create_time, dish.update_time, dish.create_user, dish.update_user, category.name from dish right join category on dish.category_id = category.id where dish.name = '' or category.name = ''

        // 1、构造分页构造器
        Page<Dish> pageInfo = new Page<>(page, pageSize);
        Page<DishDto> dishDtoPage = new Page<>();
        // 2、构造条件构造器
        LambdaQueryWrapper<Dish> dishQueryWrapper = new LambdaQueryWrapper<>();
        // 3、过滤
        dishQueryWrapper.like(name != null, Dish::getName, name);
        // 4、排序
        dishQueryWrapper.orderByDesc(Dish::getUpdateTime);
        // 5、查询
        dishService.page(pageInfo, dishQueryWrapper);
        // 6、对象拷贝
        BeanUtils.copyProperties(pageInfo, dishDtoPage, "records");
        // 7、处理records
        List<Dish> records = pageInfo.getRecords();
        List<DishDto> list = records.stream().map((dish) -> {
            DishDto dishDto = new DishDto();
            // 拷贝
            BeanUtils.copyProperties(dish, dishDto);
            Long categoryId = dish.getCategoryId(); // 分类id
            Category category = categoryService.getById(categoryId); // 分类对象
            if (null != category) {
                String categoryName = category.getName();
                dishDto.setCategoryName(categoryName);
            }
            return dishDto;
        }).collect(Collectors.toList());
        // 8、封装
        return dishDtoPage.setRecords(list);
    }

    /**
     * 操作套餐数据时，查询菜品
     */
    /*@Override
    public R<List<Dish>> listDish(Dish dish) {
        // 1、构建查询条件
        LambdaQueryWrapper<Dish> dishMapper = new LambdaQueryWrapper<>();
        dishMapper.eq(dish.getCategoryId() != null, Dish::getCategoryId, dish.getCategoryId())
                .or().eq(Dish::getName, dish.getName());
        dishMapper.eq(Dish::getStatus, 1);
        // 2、排序
        dishMapper.orderByAsc(Dish::getSort).orderByDesc(Dish::getUpdateTime);
        List<Dish> list = dishService.list(dishMapper);
        if (null != list) {
            return R.success(list);
        }
        return R.error("查询失败");
    }*/
    // 改造
    @Override
    public R<List<DishDto>> listDish(Dish dish) {
        // 1、构建查询条件
        LambdaQueryWrapper<Dish> dishMapper = new LambdaQueryWrapper<>();
        dishMapper.eq(dish.getCategoryId() != null, Dish::getCategoryId, dish.getCategoryId())
                .or().eq(Dish::getName, dish.getName());
        dishMapper.eq(Dish::getStatus, 1);
        // 2、排序
        dishMapper.orderByAsc(Dish::getSort).orderByDesc(Dish::getUpdateTime);
        List<Dish> list = dishService.list(dishMapper);
        // 3、扩展数据
        List<DishDto> dishDtoList = list.stream().map((item) -> {
            DishDto dishDto = new DishDto();
            // 3.1 拷贝
            BeanUtils.copyProperties(item, dishDto);
            Long categoryId = item.getCategoryId(); // 分类id
            Category category = categoryService.getById(categoryId); // 分类对象
            if (null != category) {
                String categoryName = category.getName();
                dishDto.setCategoryName(categoryName);
            }
            // 4、当前菜品id
            Long dishId = item.getId();
            LambdaQueryWrapper<DishFlavor> dishFlavorWrapper = new LambdaQueryWrapper<>();
            dishFlavorWrapper.eq(DishFlavor::getDishId, dishId);
            // 4、1 查询口味数据
            List<DishFlavor> dishFlavorList = dishFlavorService.list(dishFlavorWrapper);
            dishDto.setFlavors(dishFlavorList);
            return dishDto;
        }).collect(Collectors.toList());
        return R.success(dishDtoList);
    }
}
